﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using DevExpress.XtraEditors;
using DevExpress.XtraGrid;
using DevExpress.XtraGrid.Views.Grid;
using DevExpress.XtraGrid.Views.Grid.ViewInfo;
using DevExpress.XtraGrid.Columns;
using DevExpress.XtraGrid.Views.Base;
using DevExpress.XtraTreeList.Nodes;
using Model;

namespace TanHungLong
{
    public partial class FrmQuyenHan : DevExpress.XtraEditors.XtraForm
    {
        #region variant
        private FormStatus formStatus = FormStatus.View;
        private bool allowCloseForm = true;
        private DanhMucBOCollection danhMucBOCollection = null;
        private PhanQuyenBOCollection phanQuyenBOCollection = null;
        private PhanQuyenBOCollection tmpPhanQuyenBOCollection = null;

        private string COLUMN_FIRST = "Ten";
        private string COLUMN_SECOND = "STT0";
        private bool flag = true;
        #endregion variant

        //=====================================
        #region form
        public FrmQuyenHan()
        {
            InitializeComponent();
            this.KeyPreview = true;

            this.Load += new EventHandler(FrmQuyenHan_Load);
            this.Shown += new EventHandler(FrmQuyenHan_Shown);
            this.FormClosing += new FormClosingEventHandler(FrmQuyenHan_FormClosing);
            this.KeyDown += new KeyEventHandler(FrmQuyenHan_KeyDown);

            this.btnRefresh.Click += new EventHandler(btnRefresh_Click);
            this.btnEdit.Click += new EventHandler(btnEdit_Click);
            this.btnSave.Click += new EventHandler(btnSave_Click);
            this.btnCancel.Click += new EventHandler(btnCancel_Click);
            this.btnClose.Click += new EventHandler(btnClose_Click);

            this.gridViewDanhMuc.RowCellStyle += new RowCellStyleEventHandler(gridViewDanhMuc_RowCellStyle);
            this.gridViewDanhMuc.ShowingEditor += new CancelEventHandler(gridViewDanhMuc_ShowingEditor);
        }

        private void FrmQuyenHan_Shown(object sender, EventArgs e)
        {
            this.gridViewDanhMuc.Focus();
        }

        private void FrmQuyenHan_KeyDown(object sender, KeyEventArgs e)
        {
            if (this.btnClose.Visible && ((e.KeyCode == Keys.Q && Control.ModifierKeys == Keys.Control) || (e.KeyCode == Keys.F10)))
                this.Close();
            else
                if (this.btnRefresh.Visible && ((e.KeyCode == Keys.R && Control.ModifierKeys == Keys.Control) || (e.KeyCode == Keys.F5)))
                    RefreshData();
                else
                    if (this.btnSave.Visible && ((e.KeyCode == Keys.S && Control.ModifierKeys == Keys.Control) || (e.KeyCode == Keys.F6)))
                        Save();
                    else
                        if (this.btnEdit.Visible && ((e.KeyCode == Keys.E && Control.ModifierKeys == Keys.Control) || (e.KeyCode == Keys.F2)))
                            Edit();
                        else
                            if (this.btnCancel.Visible && ((e.KeyCode == Keys.H && Control.ModifierKeys == Keys.Control) || (e.KeyCode == Keys.F12)))
                                Cancel();
        }

        private void FrmQuyenHan_Load(object sender, EventArgs e)
        {
            MyStyle.SetGridStyle(this.gridViewDanhMuc, false);

            RefreshData();
            SetFormStatus(this.formStatus);

            this.gridViewDanhMuc.FocusedRowChanged += new FocusedRowChangedEventHandler(gridViewDanhMuc_FocusedRowChanged);
            this.gridViewDanhMuc.InitNewRow += new InitNewRowEventHandler(gridViewDanhMuc_InitNewRow);
            this.treeListPhanQuyen.CellValueChanging += new DevExpress.XtraTreeList.CellValueChangedEventHandler(treeListPhanQuyen_CellValueChanging);
        }

        private void FrmQuyenHan_FormClosing(object sender, FormClosingEventArgs e)
        {
            if (this.allowCloseForm == false)
                e.Cancel = true;
        }
        #endregion form

        //=====================================
        #region control
        #endregion control

        //=====================================
        #region button
        private void btnRefresh_Click(object sender, EventArgs e)
        {
            RefreshData();
        }

        private void btnEdit_Click(object sender, EventArgs e)
        {
            Edit();
        }

        private void btnSave_Click(object sender, EventArgs e)
        {
            Save();
        }

        private void btnCancel_Click(object sender, EventArgs e)
        {
            Cancel();
        }

        private void btnClose_Click(object sender, EventArgs e)
        {
            this.Close();
        }
        #endregion button

        //=====================================
        #region grid
        private void treeListPhanQuyen_CellValueChanging(object sender, DevExpress.XtraTreeList.CellValueChangedEventArgs e)
        {
            if (e.Column.FieldName == "TruyCap")
                if (this.flag)
                    if (e.Node.HasChildren)
                    {
                        this.flag = false;
                        bool check = StaticUtil.GetBool(e.Value);
                        SetNodeState(e.Node, check);
                        this.flag = true;
                    }
        }

        private void gridViewDanhMuc_InitNewRow(object sender, InitNewRowEventArgs e)
        {
            int? QuyenHanID = StaticUtil.GetRealInt(this.gridViewDanhMuc.GetRowCellValue(e.RowHandle, "DanhMucID"));
            if (QuyenHanID != null)
            {
                CreatePhanQuyen(QuyenHanID.Value);
                Session.QuyenHanID = QuyenHanID;
                FilterDanhMuc();
            }
        }

        private void gridViewDanhMuc_FocusedRowChanged(object sender, FocusedRowChangedEventArgs e)
        {
            FilterDanhMuc();
        }

        private void gridViewDanhMuc_ShowingEditor(object sender, CancelEventArgs e)
        {
            bool del = StaticUtil.GetBool(this.gridViewDanhMuc.GetFocusedRowCellValue("DELE"));
            string fieldName = this.gridViewDanhMuc.FocusedColumn.FieldName;

            if (del && fieldName != "DELE")
                e.Cancel = true;
            else
                if (fieldName == "DELE" && this.gridViewDanhMuc.FocusedRowHandle == GridControl.NewItemRowHandle)
                    e.Cancel = true;
        }

        private void gridViewDanhMuc_RowCellStyle(object sender, RowCellStyleEventArgs e)
        {
            bool del = StaticUtil.GetBool(this.gridViewDanhMuc.GetRowCellValue(e.RowHandle, "DELE"));

            if (del)
            {
                e.Appearance.Font = MyStyle.DELETE_FONT;
                e.Appearance.ForeColor = MyStyle.DELETE_COLOR;
            }
        }
        #endregion grid

        //=====================================
        #region function
        private void FilterDanhMuc()
        {
            Session.QuyenHanID = StaticUtil.GetRealInt(this.gridViewDanhMuc.GetFocusedRowCellValue("DanhMucID"));
            if (Session.QuyenHanID == null)
                this.bdSourcePhanQuyen.DataSource = null;
            else
                this.bdSourcePhanQuyen.DataSource = this.tmpPhanQuyenBOCollection.GetData(Session.QuyenHanID.Value);

            this.treeListPhanQuyen.ExpandAll();
        }

        private void RefreshData()
        {
            this.danhMucBOCollection = DanhMucBOCollection.GetDanhMucBOCollection("LoaiDanhMuc=N'" + StaticUtil.GetLoaiDanhMuc(LoaiDanhMuc.QuyenHan) + "'");
            this.phanQuyenBOCollection = PhanQuyenBOCollection.GetPhanQuyenBOCollection("", "QuyenHanID,ModuleID");

            this.danhMucBOCollection.SttIndex = this.danhMucBOCollection.Count;
            this.bdSourceDanhMuc.DataSource = this.danhMucBOCollection.Clone();

            this.tmpPhanQuyenBOCollection = this.phanQuyenBOCollection.Clone();
            this.bdSourcePhanQuyen.DataSource = null;

            FilterDanhMuc();
        }

        private void Edit()
        {
            this.formStatus = FormStatus.Edit;
            SetFormStatus(this.formStatus);
            Session.CloseIndex++;
        }

        private void Save()
        {
            string oldColumn = this.gridViewDanhMuc.FocusedColumn.FieldName;
            string newColumn = (oldColumn == this.COLUMN_FIRST ? this.COLUMN_SECOND : this.COLUMN_FIRST);
            this.gridViewDanhMuc.FocusedColumn = this.gridViewDanhMuc.Columns[newColumn];

            this.bdSourceDanhMuc.EndEdit();
            this.bdSourcePhanQuyen.EndEdit();

            int i = 0;
            int length = 0;
            string loaiDanhMuc = StaticUtil.GetLoaiDanhMuc(LoaiDanhMuc.QuyenHan);

            this.danhMucBOCollection = (DanhMucBOCollection)this.bdSourceDanhMuc.DataSource;
            length = this.danhMucBOCollection.Count;
            for (i = 0; i < length; i++)
                this.danhMucBOCollection[i].LoaiDanhMuc = loaiDanhMuc;

            this.danhMucBOCollection = this.danhMucBOCollection.Save();
            this.danhMucBOCollection.SttIndex = this.danhMucBOCollection.Count;



            this.phanQuyenBOCollection = this.tmpPhanQuyenBOCollection;
            int dataLength = this.phanQuyenBOCollection.lstData.Count;
            int ID = -1;
            int j = 0;

            for (i = 0; i < dataLength; i++)
            {
                length = this.phanQuyenBOCollection.lstData[i].Count;
                for (j = 0; j < length; j++)
                {
                    ID = this.phanQuyenBOCollection.lstData[i][j].QuyenHanID.Value;
                    if (this.danhMucBOCollection.hstID.ContainsKey(ID))
                        this.phanQuyenBOCollection.lstData[i][j].QuyenHanID = (int)this.danhMucBOCollection.hstID[ID];
                    else
                        this.phanQuyenBOCollection.lstData[i][j].DELE = true;
                }
            }
            this.phanQuyenBOCollection.SaveData();

            length = this.phanQuyenBOCollection.lstQuyenHanID.Count;
            for (i = 0; i < length; i++)
            {
                ID = this.phanQuyenBOCollection.lstQuyenHanID[i];
                if (this.danhMucBOCollection.hstID.ContainsKey(ID))
                    this.phanQuyenBOCollection.lstQuyenHanID[i] = (int)this.danhMucBOCollection.hstID[ID];
            }


            this.tmpPhanQuyenBOCollection = this.phanQuyenBOCollection.Clone();

            this.bdSourceDanhMuc.DataSource = this.danhMucBOCollection.Clone();
            this.bdSourcePhanQuyen.DataSource = null;

            this.gridViewDanhMuc.FocusedColumn = this.gridViewDanhMuc.Columns[oldColumn];

            this.formStatus = FormStatus.View;
            SetFormStatus(this.formStatus);
            Session.CloseIndex--;

            this.gridViewDanhMuc.CheckLoaded();
            FilterDanhMuc();
        }

        private void Cancel()
        {
            this.formStatus = FormStatus.View;
            SetFormStatus(this.formStatus);
            Session.CloseIndex--;
            this.bdSourceDanhMuc.DataSource = this.danhMucBOCollection.Clone();

            this.bdSourceDanhMuc.DataSource = this.danhMucBOCollection.Clone();
            this.bdSourcePhanQuyen.DataSource = null;
            FilterDanhMuc();
        }

        private void SetFormStatus(FormStatus formStatus)
        {
            bool edit = (formStatus != FormStatus.View);
            this.allowCloseForm = !edit;

            MyStyle.SetGridStyle(this.gridViewDanhMuc, edit);

            this.btnEdit.Visible = !edit;
            this.btnClose.Visible = !edit;
            this.btnRefresh.Visible = !edit;

            this.btnSave.Visible = edit;
            this.btnCancel.Visible = edit;

            this.colDELE.Visible = edit;
            this.colSTT0.OptionsColumn.AllowFocus = !edit;
            foreach (GridColumn col in this.gridViewDanhMuc.Columns)
            {
                if (col.Visible)
                    col.OptionsColumn.AllowEdit = edit;
            }

            this.colTenModule.OptionsColumn.AllowFocus = !edit;
            this.colTruyCap.OptionsColumn.AllowEdit = edit;


            this.gridViewDanhMuc.OptionsView.NewItemRowPosition = (edit ? NewItemRowPosition.Bottom : NewItemRowPosition.None);
            this.gridViewDanhMuc.Focus();

            if (edit)
            {
                string focusColumn = this.gridViewDanhMuc.FocusedColumn.FieldName;

                if (string.IsNullOrEmpty(focusColumn))
                    focusColumn = this.COLUMN_FIRST;
                else
                    if (focusColumn == "DELE")
                        focusColumn = this.COLUMN_FIRST;

                if (this.gridViewDanhMuc.RowCount == 1)
                    this.gridViewDanhMuc.FocusedRowHandle = int.MinValue + 1;

                this.gridViewDanhMuc.FocusedColumn = this.gridViewDanhMuc.Columns[focusColumn];
                this.gridViewDanhMuc.ShowEditor();
            }
        }

        private void CreatePhanQuyen(int QuyenHanID)
        {
            int length = Session.lstModuleItem.Count;
            this.bdSourcePhanQuyen.EndEdit();
            PhanQuyenBOCollection phanQuyenBOCollection = PhanQuyenBOCollection.NewPhanQuyenBOCollection();

            ModuleItem item = null;
            for (int i = 0; i < length; i++)
            {
                item = Session.lstModuleItem[i];

                PhanQuyenBO phanQuyenBO = PhanQuyenBOCollection.NewPhanQuyenBO();
                phanQuyenBO.QuyenHanID = QuyenHanID;
                phanQuyenBO.ModuleID = item.ModuleID;
                phanQuyenBO.ParentID = item.ModuleID / 1000;
                phanQuyenBO.Ten = item.Ten;

                phanQuyenBOCollection.Add(phanQuyenBO);
            }

            this.tmpPhanQuyenBOCollection.lstQuyenHanID.Add(QuyenHanID);
            this.tmpPhanQuyenBOCollection.lstData.Add(phanQuyenBOCollection.Clone());

            this.bdSourcePhanQuyen.DataSource = phanQuyenBOCollection;
        }

        private void SetNodeState(TreeListNode node, bool check)
        {
            node.SetValue(this.colTruyCap, check);
            if (node.HasChildren)
            {
                int length = node.Nodes.Count;
                for (int i = 0; i < length; i++)
                    SetNodeState(node.Nodes[i], check);
            }
        }
        #endregion function
    }
}